package com.axxc.jpa.service;

import java.io.Serializable;
import java.util.ArrayList;
import java.util.List;

import javax.transaction.Transactional;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.domain.Page;
import org.springframework.data.domain.PageImpl;
import org.springframework.data.domain.Pageable;
import org.springframework.data.jpa.domain.Specification;

import com.alibaba.fastjson.JSONObject;
import com.axxc.jpa.repository.ISimpleCRUDRepository;

/**
 * @ClassName: AbstractCRUDService
 * @Description: TODO(这里用一句话描述这个类的作用)
 * @author 熊小川
 * @date 2018年5月13日 下午2:03:19
 */
@Transactional
public abstract class AbstractCRUDService<M, E, F, ID extends Serializable> implements ISimpleCRUDService<M, F, ID> {

	protected Logger logger = LoggerFactory.getLogger(getClass());

	@Autowired(required = false)
	protected ISimpleCRUDRepository<E, ID> repository;

	@Override
	public void insertIntoDB(M target) {
		// TODO 插入数据到数据库
		logger.debug("insert Object:" + JSONObject.toJSONString(target));

		E entity = this.toEntity(target);

		this.repository.save(entity);
	}

	@Override
	public Long count(F filter) {
		return this.repository.count(this.toFilter(filter));
	}

	@Override
	public Page<M> search(F filter, Pageable pageable) {
		// TODO 分页查询
		Page<M> views;
		List<M> content;

		Page<E> entitys = this.repository.findAll(this.toFilter(filter), pageable);
		content = new ArrayList<>();
		M v;
		for (E e : entitys) {
			v = this.toModel(e);
			content.add(v);
		}
		views = new PageImpl<>(content, pageable, entitys.getTotalElements());

		return views;

	}

	protected abstract E toEntity(M model);

	protected abstract M toModel(E entity);

	protected abstract Specification<E> toFilter(F filter);

}
